#include <stdint.h>
#include <stdio.h>
#include <string.h>

#include "pskeys.h"

#include "os_mem.h"
#include "driver_plf.h"
#include "driver_syscntl.h"
#include "driver_flash.h"
#include "driver_wdt.h"
#include "driver_uart.h"
#include "driver_flash_ssp.h"
#include "driver_ssp.h"
#include "driver_gpio.h"
#include "driver_iomux.h"

#include "gatt_api.h"
#include "gap_api.h"

#include "user_utils.h"

#include "ota_flash.h"
#include "ota_flash_service.h"
#include "user_config.h"

// SSP函数声明
extern void ssp_put_data(uint8_t data);
extern void ssp_get_data(uint8_t *data);
extern void ssp_enable(void);
extern void ssp_disable(void);
extern void ssp_wait_busy_bit(void);

// 宏定义控制：是否使用手动控制CSN的方式写入Flash
#define USE_MANUAL_CSN_CONTROL    1

// SSP寄存器结构体定义（用于手动控制CSN）- 与dsp_program.c完全一致
#if USE_MANUAL_CSN_CONTROL == 1
typedef unsigned int    u32;
typedef unsigned short  u16;
typedef unsigned char   u8;

struct ssp_cr0{
    u32 dss:4;  /* data size select : = DATASIZE - 1*/
    u32 frf:2;  /* frame format */
    u32 spo:1;  /* sclk polarity */
    u32 sph:1;  /* sclk phase */
    u32 scr:8;  /* serial clock rate */
    u32 unused:16;
};

struct ssp_cr1{
    u32 rie:1;  /* rx fifo interrupt enable */
    u32 tie:1;  /* tx fifo interrupt enable */
    u32 rorie:1;/* rx fifo overrun interrupt enable */
    u32 lbm:1;  /* loop back mode */
    u32 sse:1;  /* synchronous serial port enable*/
    u32 ms:1;   /* master mode or slave mode */
    u32 sod:1;  /* output disable in slave mode */
    u32 unused:25;
};

struct ssp_dr{
    u32 data:8; 
    u32 unused:24;
};

struct ssp_sr{
    u32 tfe:1;  /* transmit fifo empty */
    u32 tnf:1;  /* transmit fifo not full */
    u32 rne:1;  /* receive fifo not empty */
    u32 rff:1;  /* receive fifo full */
    u32 bsy:1;  /* ssp busy flag */
    u32 unused:27;
};

struct ssp_cpsr{
    u32 cpsdvsr:8;  /* clock prescale divisor 2-254 */
    u32 unused:24;
};

struct ssp_ff_int_ctrl {
    u32 rx_ff:8;
    u32 tx_ff:8;
    u32 unused:16;
};

struct ssp{
    struct ssp_cr0 ctrl0;
    struct ssp_cr1 ctrl1; /*is also error clear register*/
    struct ssp_dr data;
    struct ssp_sr status;
    struct ssp_cpsr clock_prescale;
    uint32_t reserved;
    struct ssp_ff_int_ctrl ff_ctrl;
};
#endif

// 前向声明
static uint8_t ssp_flash_read_status_reg(void);
static void flash_poll_busy_bit(void);
static void ssp_flash_write_enable(void);
static int safe_ssp_flash_erase(uint32_t addr, uint32_t size);
static int safe_ssp_flash_write(uint32_t addr, uint8_t *data, uint32_t len);

// 简化的命令处理函数声明
static void ota_handle_get_version(uint8_t conidx);
static void ota_handle_erase_flash(uint8_t conidx, uint32_t addr, uint32_t size);
static void ota_handle_write_data(uint8_t conidx, uint32_t addr, uint16_t len, uint8_t *data);
static void ota_handle_read_data(uint8_t conidx, uint32_t addr, uint16_t len);
static void ota_handle_reboot(uint8_t conidx);
static void ota_handle_error(uint8_t conidx, uint8_t cmd, uint32_t addr, uint16_t len);
static void ota_send_response(uint8_t conidx, uint16_t response_len);

// 外部函数声明
extern uint8_t ssp_flash_erase(uint32_t addr, uint32_t size);
extern uint8_t ssp_flash_write(uint32_t addr, uint32_t len, uint8_t *data);
extern uint8_t ssp_flash_read(uint32_t addr, uint32_t len, uint8_t *data);  // 添加外部声明

flash_version_t flash_ver = {0xff,0xff,0xff};
static bool is_ota_run = false;
void ota_flash_var_reset(){

    is_ota_run = false;
}



// SSP引脚初始化函数
static void ota_flash_ssp_pin_init(void)
{
	
	#if FR5086D_V2_0
    // 配置SSP引脚复用功能
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_0, PORTA0_FUNC_SSP_SCLK);  // SCLK
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_SSP_CSN);   // CSN
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_2, PORTA2_FUNC_SSP_MOSI);  // MOSI
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_3, PORTA3_FUNC_SSP_MISO);  // MISO
    
    // 配置额外的控制引脚（如果需要）
    system_set_port_mux(GPIO_PORT_D, GPIO_BIT_6, PORTD6_FUNC_D6);
    system_set_port_mux(GPIO_PORT_D, GPIO_BIT_7, PORTD7_FUNC_D7);
    gpio_set_dir(GPIO_PORT_D, GPIO_BIT_6, GPIO_DIR_OUT);
    gpio_set_dir(GPIO_PORT_D, GPIO_BIT_7, GPIO_DIR_OUT);
    gpio_set_pin_value(GPIO_PORT_D, GPIO_BIT_6, 1);
    gpio_set_pin_value(GPIO_PORT_D, GPIO_BIT_7, 1);
	#endif
	
	
		#if FR5082DM_V1_0
	
	
	//配置SSP引脚复用功能
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_0, PORTA0_FUNC_SSP_SCLK);  // SCLK
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_SSP_CSN);   // CSN
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_2, PORTA2_FUNC_SSP_MOSI);  // MOSI
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_3, PORTA3_FUNC_SSP_MISO);  // MISO
    
    // 配置额外的控制引脚（如果需要）
    system_set_port_mux(GPIO_PORT_D, GPIO_BIT_6, PORTD6_FUNC_D6);
    system_set_port_mux(GPIO_PORT_D, GPIO_BIT_7, PORTD7_FUNC_D7);
    gpio_set_dir(GPIO_PORT_D, GPIO_BIT_6, GPIO_DIR_OUT);
    gpio_set_dir(GPIO_PORT_D, GPIO_BIT_7, GPIO_DIR_OUT);
    gpio_set_pin_value(GPIO_PORT_D, GPIO_BIT_6, 1);
    gpio_set_pin_value(GPIO_PORT_D, GPIO_BIT_7, 1);

#endif  // FR5082DM_V1_0
	
	
	
	
    
    printf("External Flash OTA: SSP pins initialized\r\n");
}

// SSP引脚恢复函数
static void ota_flash_ssp_pin_recover(void)
{
		#if FR5086D_V2_0
    // 恢复引脚为默认功能
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_0, PORTA0_FUNC_A0);
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_A1);
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_2, PORTA2_FUNC_A2);
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_3, PORTA3_FUNC_A3);
    gpio_set_dir(GPIO_PORT_D, GPIO_BIT_6, GPIO_DIR_IN);
    gpio_set_dir(GPIO_PORT_D, GPIO_BIT_7, GPIO_DIR_IN);
	
	#endif
	
	#if FR5082DM_V1_0
	
	    // 恢复引脚为默认功能
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_0, PORTA0_FUNC_A0);
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_A1);
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_2, PORTA2_FUNC_A2);
    system_set_port_mux(GPIO_PORT_A, GPIO_BIT_3, PORTA3_FUNC_A3);
    gpio_set_dir(GPIO_PORT_D, GPIO_BIT_6, GPIO_DIR_IN);
    gpio_set_dir(GPIO_PORT_D, GPIO_BIT_7, GPIO_DIR_IN);
 
	#endif  // FR5082DM_V1_0
    
    printf("External Flash OTA: SSP pins recovered\r\n");
}

// SSP寄存器访问测试函数
static void test_ssp_register_access(void)
{
    volatile struct ssp * const ssp = (volatile struct ssp *)SSP_BASE;
    
    printf("External Flash SSP register access test:\r\n");
    printf("SSP base address: 0x%08X\r\n", (uint32_t)ssp);
    
    // 测试读取寄存器
    // uint32_t ctrl0_read = (uint32_t)ssp->ctrl0;
    // uint32_t ctrl1_read = (uint32_t)ssp->ctrl1;
    // uint32_t status_read = (uint32_t)ssp->status;
    
    // printf("SSP register read test - ctrl0: 0x%08X, ctrl1: 0x%08X, status: 0x%08X\r\n", 
    //        ctrl0_read, ctrl1_read, status_read);
    
    // 测试写入寄存器（临时测试）
    // GLOBAL_INT_DISABLE();
    // ssp->ctrl0 = (struct ssp_cr0)0x00000007;  // 设置8位数据位
    // ssp->ctrl1 = (struct ssp_cr1)0x00000002;  // 启用SSP，主模式
    // GLOBAL_INT_RESTORE();
    
    // 再次读取验证
    // ctrl0_read = (uint32_t)ssp->ctrl0;
    // ctrl1_read = (uint32_t)ssp->ctrl1;
    // status_read = (uint32_t)ssp->status;
    
    // printf("SSP register write test - ctrl0: 0x%08X, ctrl1: 0x%08X, status: 0x%08X\r\n", 
    //        ctrl0_read, ctrl1_read, status_read);
    
    // 恢复寄存器状态
    // GLOBAL_INT_DISABLE();
    // ssp->ctrl0 = (struct ssp_cr0)0;
    // ssp->ctrl1 = (struct ssp_cr1)0;
    // GLOBAL_INT_RESTORE();
}

static struct app_otas_flash_status_t
{
    uint8_t read_opcode;
    uint16_t length;
    uint32_t base_addr;
} app_otas_flash_status;

static struct buffed_flash_pkt
{
    uint8_t *buf;
    uint16_t len;   //current length in the buffer
    uint16_t malloced_pkt_num;  //num of pkts
} first_flash_pkt = {0};

static uint8_t first_flash_loop = false;
static uint16_t ota_flash_data_idx;
static bool ota_flash_recving_data = false;
static uint16_t ota_flash_recving_data_index = 0;
static uint16_t ota_flash_recving_expected_length = 0;
static uint8_t *ota_flash_recving_buffer = NULL;

// 新增：跟踪实际写入的数据量
static uint32_t total_written_bytes = 0;
static uint32_t last_written_addr = 0;

extern uint8_t app_boot_get_storage_type(void);
extern void app_boot_save_data(uint32_t dest, uint8_t *src, uint32_t len);
extern void app_boot_load_data(uint8_t *dest, uint32_t src, uint32_t len);
extern void system_set_cache_config(uint8_t value, uint8_t count_10us);

// 外部Flash操作函数
static uint32_t app_otas_flash_get_storage_base(void)
{
    // 外部Flash基地址，可以根据实际硬件配置调整
    return 0x00000000;  // 外部Flash从0地址开始
}

__attribute__((section("ram_code"))) static void app_otas_flash_save_data(uint32_t dest, uint8_t *src, uint32_t len)
{
    // 使用SSP接口写入外部Flash
    ssp_flash_write(dest, len, src);
}

__attribute__((section("ram_code"))) static void app_otas_flash_load_data(uint32_t src, uint8_t *dest, uint32_t len)
{
    // 使用SSP接口读取外部Flash
    ssp_flash_read(src, len, dest);
}

void ota_flash_clr_buffed_pkt(uint8_t conidx)
{
    if(first_flash_pkt.buf != NULL)
    {
        first_flash_loop = true;
        os_free(first_flash_pkt.buf);
        memset(&first_flash_pkt,0x0,sizeof(first_flash_pkt));
    }
}

void ota_flash_init(uint8_t conidx)
{
    // 简化初始化，不需要设置read_opcode
    first_flash_loop = true;
    ota_flash_data_idx = 0;
    
    // 重置写入统计信息
    total_written_bytes = 0;
    last_written_addr = 0;
    
    #if 0
    // 初始化SSP引脚
    ota_flash_ssp_pin_init();
    
    // 初始化SSP控制器
    ssp_init(8, 0, 0, 500000, 2, 0);  // 8位数据位，无极性，无相位，500KHz时钟，2字节FIFO阈值
    
    // 初始化外部Flash SSP接口
    ssp_flash_init();
    #else


    // flash_ver.major = 0xff;
    // flash_ver.minor = 0xff;
    // flash_ver.patch = 0xff;



    #endif
    printf("External Flash OTA: SSP Flash initialized\r\n");
}

void ota_flash_deinit(uint8_t conidx)
{
    ota_flash_clr_buffed_pkt(conidx);

    if(ota_flash_recving_buffer != NULL)
    {
        os_free(ota_flash_recving_buffer);
        ota_flash_recving_buffer = NULL;
    }
    
    // 恢复SSP引脚
    //ota_flash_ssp_pin_recover();
}

void __attribute__((weak)) ota_flash_change_flash_pin(void)
{
    // 在Flash操作前，确保引脚配置正确
    // 这里可以添加额外的引脚控制逻辑，比如使能Flash芯片等
    ;
}

void __attribute__((weak)) ota_flash_recover_flash_pin(void)
{
    // 在Flash操作后，恢复引脚状态
    // 这里可以添加额外的引脚恢复逻辑
    ;
}

// 简化的数据接收处理 - 替换原有的复杂协议解析
void app_otas_flash_recv_data(uint8_t conidx, uint8_t *p_data, uint16_t len) {
    if (len < 7) {  // 最小命令长度：cmd(1) + addr(4) + len(2)
        printf("External Flash OTA: Command length insufficient, len=%d\r\n", len);
        return;
    }
    wdt_feed();
    // 解析命令
    uint8_t command = p_data[0];
    uint16_t length = (p_data[2] << 8) | p_data[1];  // 小端序
    uint32_t addr = (p_data[6] << 24) | (p_data[5] << 16) | (p_data[4] << 8) | p_data[3];  // 小端序
    
    printf("External Flash OTA: Received command cmd=0x%02X, addr=0x%08X, len=%d\r\n", command, addr, length);
    
    // 根据命令类型处理
    switch (command) {
        case OTA_FLASH_CMD_GET_VERSION:
            printf("External Flash OTA: Processing get version command\r\n");
            ota_handle_get_version(conidx);
            break;
            
        case OTA_FLASH_CMD_ERASE_FLASH:


        #if 1


        if(!is_ota_run){

            system_sleep_disable();
            dsp_close();
					
					
						#if FR5086D_V2_0

            // 先恢复所有引脚为默认状态
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_0, PORTA0_FUNC_A0);
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_A1);
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_2, PORTA2_FUNC_A2);
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_3, PORTA3_FUNC_A3);
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_4, PORTA4_FUNC_A4);
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_5, PORTA5_FUNC_A5);
					#endif
					
					
					#if  FR5082DM_V1_0
					
					  //system_set_port_mux(GPIO_PORT_D, GPIO_BIT_6, PORTD6_FUNC_QSPI1_MISO2);
						//system_set_port_mux(GPIO_PORT_D, GPIO_BIT_7, PORTD7_FUNC_QSPI1_MISO3);
					
					
					     // 先恢复所有引脚为默认状态
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_0, PORTA0_FUNC_A0);
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_A1);
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_2, PORTA2_FUNC_A2);
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_3, PORTA3_FUNC_A3);
            system_set_port_mux(GPIO_PORT_D, GPIO_BIT_6, PORTD6_FUNC_D6);
            system_set_port_mux(GPIO_PORT_D, GPIO_BIT_7, PORTD7_FUNC_D7);
					
					#endif
					

            // 初始化SSP引脚
            ota_flash_ssp_pin_init();
            
            // 初始化SSP控制器
            ssp_init(8, 0, 0, 500000, 2, 0);  // 8位数据位，无极性，无相位，500KHz时钟，2字节FIFO阈值
            
            // 初始化外部Flash SSP接口
            ssp_flash_init();
            is_ota_run = true;
        }
        #endif


            printf("External Flash OTA: Processing erase command, sectors=%d\r\n", length);
            // 对于擦除命令，length字段表示要擦除的扇区数，addr字段表示起始地址
            uint32_t erase_size = length * 0x1000;  // 每个扇区4KB
            ota_handle_erase_flash(conidx, addr, erase_size);
            break;
            
        case OTA_FLASH_CMD_WRITE_DATA:
            printf("External Flash OTA: Processing write command, data length=%d\r\n", length);
            if (len >= 9 + length) {  // 命令头9字节 + 数据长度
                // 对于写入命令，地址在p_data[3-6]，数据长度在p_data[7-8]
                uint32_t write_addr = (p_data[6] << 24) | (p_data[5] << 16) | (p_data[4] << 8) | p_data[3];
                uint16_t data_len = (p_data[8] << 8) | p_data[7];
                ota_handle_write_data(conidx, write_addr, data_len, &p_data[9]);
            } else {
                printf("External Flash OTA: Write data length mismatch\r\n");
                ota_handle_error(conidx, command, addr, length);
            }
            break;
            
        case OTA_FLASH_CMD_READ_DATA:
            printf("External Flash OTA: Processing read command, read length=%d\r\n", length);
            if (len >= 9) {
                // 对于读取命令，地址在p_data[3-6]，读取长度在p_data[7-8]
                uint32_t read_addr = (p_data[6] << 24) | (p_data[5] << 16) | (p_data[4] << 8) | p_data[3];
                uint16_t read_len = (p_data[8] << 8) | p_data[7];
                ota_handle_read_data(conidx, read_addr, read_len);
            } else {
                ota_handle_error(conidx, command, addr, length);
            }
            break;
            
        case OTA_FLASH_CMD_REBOOT:
            printf("External Flash OTA: Processing reboot command\r\n");
            ota_handle_reboot(conidx);
            break;
            
        default:
            printf("External Flash OTA: Unknown command 0x%02X\r\n", command);
            ota_handle_error(conidx, command, addr, length);
            break;
    }
}

// 简化的命令处理函数
static void ota_handle_get_version(uint8_t conidx) {
    // 分配响应缓冲区
    if (ota_flash_recving_buffer == NULL) {
        ota_flash_recving_buffer = os_malloc(OTAS_FLASH_MAX_DATA_SIZE);
        if (ota_flash_recving_buffer == NULL) {
            printf("External Flash OTA: Memory allocation failed\r\n");
            return;
        }
    }
    
    ota_flash_rsp_t *rsp = (ota_flash_rsp_t *)ota_flash_recving_buffer;
    ota_flash_version_t *version = (ota_flash_version_t *)(rsp + 1);
    
    // 设置响应头
    rsp->result = OTA_FLASH_RSP_SUCCESS;
    rsp->cmd = OTA_FLASH_CMD_GET_VERSION;
    rsp->addr = 0x00000000;  // 版本信息地址
    rsp->len = sizeof(ota_flash_version_t);
    
    // 设置版本信息

    version->major = flash_ver.major ;
    version->minor = flash_ver.minor;
    version->patch = flash_ver.patch;
    version->base_addr = app_otas_flash_get_storage_base();
    
    printf("External Flash OTA: Version info - %d.%d.%d, Base address=0x%08X\r\n", 
           version->major, version->minor, version->patch, version->base_addr);
    
    // 发送响应
    ota_send_response(conidx, sizeof(ota_flash_rsp_t) + sizeof(ota_flash_version_t));
}

static void ota_handle_erase_flash(uint8_t conidx, uint32_t addr, uint32_t size) {
    // 分配响应缓冲区
    if (ota_flash_recving_buffer == NULL) {
        ota_flash_recving_buffer = os_malloc(OTAS_FLASH_MAX_DATA_SIZE);
        if (ota_flash_recving_buffer == NULL) {
            printf("External Flash OTA: Memory allocation failed\r\n");
            return;
        }
    }
    
    ota_flash_rsp_t *rsp = (ota_flash_rsp_t *)ota_flash_recving_buffer;
    
    printf("External Flash OTA: Starting Flash erase, address=0x%08X, size=%d bytes\r\n", addr, size);
    
    // 执行Flash擦除
    int result = safe_ssp_flash_erase(addr, size);
    
    // 设置响应
    rsp->result = (result == 0) ? OTA_FLASH_RSP_SUCCESS : OTA_FLASH_RSP_ERROR;
    rsp->cmd = OTA_FLASH_CMD_ERASE_FLASH;
    rsp->addr = addr;
    rsp->len = size;
    
    printf("External Flash OTA: Erase completed, result=%s\r\n", (result == 0) ? "Success" : "Failed");
    
    // 发送响应
    ota_send_response(conidx, sizeof(ota_flash_rsp_t));
}

static void ota_handle_write_data(uint8_t conidx, uint32_t addr, uint16_t len, uint8_t *data) {
    // 分配响应缓冲区
    if (ota_flash_recving_buffer == NULL) {
        ota_flash_recving_buffer = os_malloc(OTAS_FLASH_MAX_DATA_SIZE);
        if (ota_flash_recving_buffer == NULL) {
            printf("External Flash OTA: Memory allocation failed\r\n");
            return;
        }
    }
    
    ota_flash_rsp_t *rsp = (ota_flash_rsp_t *)ota_flash_recving_buffer;
    
    printf("External Flash OTA: Starting data write, address=0x%08X, length=%d bytes\r\n", addr, len);
    
    // 执行Flash写入
    int result = safe_ssp_flash_write(addr, data, len);
    
    // 更新写入统计信息
    if (result == 0) {
        total_written_bytes += len;
        last_written_addr = addr + len;
        printf("External Flash OTA: Write stats - Total: %lu bytes, Last addr: 0x%08X\r\n", 
               (unsigned long)total_written_bytes, last_written_addr);
    }
    
    // 设置响应
    rsp->result = (result == 0) ? OTA_FLASH_RSP_SUCCESS : OTA_FLASH_RSP_ERROR;
    rsp->cmd = OTA_FLASH_CMD_WRITE_DATA;
    rsp->addr = addr;
    rsp->len = len;
    
    printf("External Flash OTA: Write completed, result=%s\r\n", (result == 0) ? "Success" : "Failed");
    
    // 发送响应
    ota_send_response(conidx, sizeof(ota_flash_rsp_t));
}

static void ota_handle_read_data(uint8_t conidx, uint32_t addr, uint16_t len) {
    // 分配响应缓冲区
    if (ota_flash_recving_buffer == NULL) {
        ota_flash_recving_buffer = os_malloc(OTAS_FLASH_MAX_DATA_SIZE);
        if (ota_flash_recving_buffer == NULL) {
            printf("External Flash OTA: Memory allocation failed\r\n");
            return;
        }
    }
    
    ota_flash_rsp_t *rsp = (ota_flash_rsp_t *)ota_flash_recving_buffer;
    uint8_t *read_data = (uint8_t *)(rsp + 1);
    
    printf("External Flash OTA: Starting data read, address=0x%08X, length=%d bytes\r\n", addr, len);
    
    // 执行Flash读取
    app_otas_flash_load_data(addr, read_data, len);
    
    // 设置响应
    rsp->result = OTA_FLASH_RSP_SUCCESS;
    rsp->cmd = OTA_FLASH_CMD_READ_DATA;
    rsp->addr = addr;
    rsp->len = len;
    
    printf("External Flash OTA: Read completed\r\n");
    
    // 发送响应（包含读取的数据）
    ota_send_response(conidx, sizeof(ota_flash_rsp_t) + len);
}

static void ota_handle_reboot(uint8_t conidx) {
    // 分配响应缓冲区
    if (ota_flash_recving_buffer == NULL) {
        ota_flash_recving_buffer = os_malloc(OTAS_FLASH_MAX_DATA_SIZE);
        if (ota_flash_recving_buffer == NULL) {
            printf("External Flash OTA: Memory allocation failed\r\n");
            return;
        }
    }
    
    ota_flash_rsp_t *rsp = (ota_flash_rsp_t *)ota_flash_recving_buffer;
    
    printf("External Flash OTA: Processing reboot command\r\n");
    
    // 设置响应
    rsp->result = OTA_FLASH_RSP_SUCCESS;
    rsp->cmd = OTA_FLASH_CMD_REBOOT;
    rsp->addr = 0x00000000;
    rsp->len = 0;
    
    printf("External Flash OTA: Reboot command processed successfully\r\n");
    
    // 发送响应
    ota_send_response(conidx, sizeof(ota_flash_rsp_t));
    
    // 清理缓冲区
    ota_flash_clr_buffed_pkt(conidx);
    
    // 延迟一段时间确保响应发送完成
    for (int i = 0; i < 1000000; i++) {
        __asm__ volatile("nop");
    }
    

    #if 0
    // === 新增：读取并打印刚刚写入的Flash数据 ===
    printf("\n=== External Flash OTA: Reading back ALL written data ===\n");
    printf("Total written: %lu bytes, Last address: 0x%08X\n", 
           (unsigned long)total_written_bytes, last_written_addr);
    
    // 读取所有写入的数据
    uint8_t read_buffer[256];  // 每次读取256字节
    
    if (total_written_bytes > 0) {
        printf("\n--- ALL written data (%lu bytes) ---\n", (unsigned long)total_written_bytes);
        
        for (uint32_t addr = 0x00000000; addr < last_written_addr; addr += 256) {
            // 计算本次读取大小
            uint32_t read_size = 256;
            if (addr + read_size > last_written_addr) {
                read_size = last_written_addr - addr;
            }
            
            // 使用SSP接口读取Flash
            ssp_flash_read(addr, read_size, read_buffer);
            
            // 打印地址和所有数据
            // printf("Addr 0x%06X: ", addr);
            for (uint32_t i = 0; i < read_size; i++) {
                printf("%02X ", read_buffer[i]);
                if ((i + 1) % 16 == 0) {
                    printf("\n         ");  // 每16字节换行
                }
            }
            printf("\n");
            
            // 每读取1KB打印一次进度
            // if ((addr + read_size) % 1024 == 0) {
            //     printf("--- Read progress: %lu/%lu bytes (%.1f%%) ---\n", 
            //            (unsigned long)(addr + read_size), (unsigned long)total_written_bytes, 
            //            (float)(addr + read_size) * 100.0f / total_written_bytes);
            // }
        }
        
        printf("\n=== External Flash OTA: ALL data readback completed (%lu bytes) ===\n\n", 
               (unsigned long)total_written_bytes);
    }

    #endif
    
    // 重启设备
    printf("External Flash OTA: Restarting device...\r\n");
    platform_reset(0);
}

static void ota_handle_error(uint8_t conidx, uint8_t cmd, uint32_t addr, uint16_t len) {
    // 分配响应缓冲区
    if (ota_flash_recving_buffer == NULL) {
        ota_flash_recving_buffer = os_malloc(OTAS_FLASH_MAX_DATA_SIZE);
        if (ota_flash_recving_buffer == NULL) {
            printf("External Flash OTA: Memory allocation failed\r\n");
            return;
        }
    }
    
    ota_flash_rsp_t *rsp = (ota_flash_rsp_t *)ota_flash_recving_buffer;
    
    // 设置错误响应
    rsp->result = OTA_FLASH_RSP_ERROR;
    rsp->cmd = cmd;
    rsp->addr = addr;
    rsp->len = len;
    
    printf("External Flash OTA: Command error, cmd=0x%02X\r\n", cmd);
    
    // 发送错误响应
    ota_send_response(conidx, sizeof(ota_flash_rsp_t));
}

// 简化的响应发送函数
static void ota_send_response(uint8_t conidx, uint16_t response_len) {
    // 分配响应缓冲区
    if (ota_flash_recving_buffer == NULL) {
        ota_flash_recving_buffer = os_malloc(OTAS_FLASH_MAX_DATA_SIZE);
        if (ota_flash_recving_buffer == NULL) {
            printf("External Flash OTA: Memory allocation failed\r\n");
            return;
        }
    }
    
    // 检查响应长度
    if (response_len > OTAS_FLASH_MAX_DATA_SIZE) {
        printf("External Flash OTA: Response too large, length=%d\r\n", response_len);
        return;
    }
    
    printf("External Flash OTA: Sending response, length=%d bytes\r\n", response_len);
    
    // 发送响应（这里需要调用实际的BLE发送函数）
    ota_flash_gatt_report_notify(conidx, ota_flash_recving_buffer, response_len);
}

uint16_t app_otas_flash_read_data(uint8_t conidx,uint8_t *p_data)
{
    // 简化实现，直接返回0表示没有数据
    return 0;
} 

// 读取Flash状态寄存器
static uint8_t ssp_flash_read_status_reg(void)
{
    uint8_t buffer[2] = {0x00, 0x00};

    ssp_put_data(0x05);  // FLASH_READ_STATUS_REG_OPCODE
    ssp_put_data(0xff);
    ssp_enable();
    ssp_wait_busy_bit();
    ssp_get_data(&buffer[0]);
    ssp_get_data(&buffer[1]);
    ssp_disable();
    
    return buffer[1];
}

// 等待Flash忙状态结束
static void flash_poll_busy_bit(void)
{
    volatile uint16_t i;
    volatile uint32_t timeout_counter = 0;
    const uint32_t max_timeout = 200;  // 最大等待次数

    while(ssp_flash_read_status_reg() & 0x03)
    {
        co_delay_10us(100);
        timeout_counter++;
        if(timeout_counter>= max_timeout){
            
             printf("External Flash poll busy timerout\r\n");
            break;
        }
    }
    
    if(timeout_counter <= max_timeout) {
        //printf("External Flash poll busy completed in %d iterations\r\n", timeout_counter);
    }
}

// 发送Flash写使能命令
static void ssp_flash_write_enable(void)
{
    uint8_t dummy;
    
    ssp_put_data(0x06);  // FLASH_WRITE_ENABLE_OPCODE
    ssp_enable();
    ssp_wait_busy_bit();
    ssp_disable();
    ssp_get_data(&dummy);
}

// 安全的SSP Flash擦除函数，包含write enable和busy等待
static int safe_ssp_flash_erase(uint32_t addr, uint32_t size)
{
    // 发送write enable命令
    ssp_flash_write_enable();
    
    // 执行擦除操作
    if(ssp_flash_erase(addr, size) != 0)
    {
        printf("External Flash erase failed at addr: 0x%08X, size: 0x%08X\r\n", addr, size);
        return -1;
    }
    
    // 等待擦除完成
    flash_poll_busy_bit();
    
    printf("External Flash erase success at addr: 0x%08X, size: 0x%08X\r\n", addr, size);
    return 0;
}



















/* ================================================================
 *  安全 Page-Program：绝不跨 256B 页；支持自动 / 手动 CSN 两种实现
 * ================================================================ */
static int safe_ssp_flash_write(uint32_t addr, uint8_t *data, uint32_t len)
{
    while (len) {
        /* ➊ 计算本页还能写多少字节 */
        uint32_t page_remain = 256 - (addr & 0xFF);
        uint32_t chunk      = (len > page_remain) ? page_remain : len;

        /* ➋ 发送 WREN */
        ssp_flash_write_enable();
        //printf("Flash write enable sent\r\n");

        /* === 新增日志：一次 Page-Program 绝不跨页 === */
        printf("PP 0x%06lX +%3luB\r\n",
            (unsigned long)addr,    /* 24-bit 起始地址，向前补 0 */
            (unsigned long)chunk);  /* 本次真正写入的字节数     */


#if USE_MANUAL_CSN_CONTROL == 0   /* ---- 自动 CSN 版本 ---- */
        /* page-program 一页 (chunk ≤ 256, 不跨页) */
        if (ssp_flash_write(addr, chunk, data) != 0) {
            printf("Flash write fail @0x%08X (%uB)\r\n", addr, chunk);
            return -1;
        }

        /* 等待内部写忙结束 */
        flash_poll_busy_bit();

#else                           /* ---- 手动 CSN 版本 ---- */
        volatile struct ssp * const ssp = (volatile struct ssp *)SSP_BASE;
        //printf("Manual CSN write: addr=0x%08X, chunk=%lu\r\n", addr, (unsigned long)chunk);
        
        /* —— 拉低 CSN —— */
        gpio_set_dir(GPIO_PORT_A, GPIO_BIT_1, GPIO_DIR_OUT);
        gpio_porta_write(gpio_porta_read() & 0xfd);          // CSN=0
        system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_A1);
        //printf("CSN pulled low\r\n");

        /* 发送 0x02 + 24-bit 地址 */
        ssp_put_data(0x02);  // FLASH_PAGE_PROGRAM_OPCODE
        ssp_put_data(addr >> 16);
        ssp_put_data(addr >> 8);
        ssp_put_data(addr);
        //printf("Flash command and address sent: 0x02 0x%02X 0x%02X 0x%02X\r\n", 
               //(addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF);

        ssp_enable();

        /* 逐字节发送 chunk 数据 */
        for (uint32_t i = 0; i < chunk; i++) {
            /* 等 TX FIFO 空 */
            uint16_t wait = 0;
            while (!ssp->status.tnf) {
                if (++wait > 1000) goto wr_timeout;
            }
            ssp->data.data = data[i];
        }
        //printf("All data sent to SSP\r\n");

        /* 等待 SPI 完全空闲 */
        while (ssp->status.bsy) ;
        //printf("SSP busy cleared\r\n");

        /* —— 拉高 CSN —— */
        system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_SSP_CSN);
        ssp_disable();
        //printf("CSN pulled high, SSP disabled\r\n");

        /* 清理FIFO */
        ssp_clear_rx_fifo();

        /* 等待内部写忙结束 */
        flash_poll_busy_bit();
        //printf("Flash busy cleared\r\n");
wr_timeout:
        if (ssp->status.bsy) {
            printf("Flash write timeout @0x%08X\r\n", addr);
            system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_SSP_CSN);
            ssp_disable();
            return -1;
        }
#endif  /* USE_MANUAL_CSN_CONTROL */

        /* ➌ 下一片段 */
        addr += chunk;
        data += chunk;
        len  -= chunk;
    }

    return 0;
}

// // 安全的SSP Flash写入函数，包含write enable和busy等待
// #if USE_MANUAL_CSN_CONTROL == 0
// static int safe_ssp_flash_write(uint32_t addr, uint8_t *data, uint32_t len)
// {
//     // 发送write enable命令
//     ssp_flash_write_enable();
    
//     // 执行写入操作
//     if(ssp_flash_write(addr, len, data) != 0)
//     {
//         printf("External Flash write failed at addr: 0x%08X, len: %d\r\n", addr, len);
//         return -1;
//     }
    
//     // 等待写入完成
//     flash_poll_busy_bit();
    
//     printf("External Flash write success at addr: 0x%08X, len: %d\r\n", addr, len);
//     return 0;
// }
// #else
// // 手动控制CSN的SSP Flash写入函数，参考dsp_program.c的实现
// static int safe_ssp_flash_write(uint32_t addr, uint8_t *data, uint32_t len)
// {
//     volatile struct ssp * const ssp = (volatile struct ssp *)SSP_BASE;
//     uint32_t remaining_len = len;
//     uint8_t *data_ptr = data;
//     volatile uint16_t timeout_counter;
    
//     printf("External Flash write start: addr=0x%08X, len=%d\r\n", addr, len);
    
//     // 发送write enable命令
//     ssp_flash_write_enable();
    
//     // 手动控制CSN信号 - 拉低CSN
//     gpio_set_dir(GPIO_PORT_A, GPIO_BIT_1, GPIO_DIR_OUT);
//     gpio_porta_write(gpio_porta_read() & 0xfd);  // 清除第1位，拉低CSN
//     system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_A1);
    
//     // 发送Flash页编程命令和地址
//     ssp_put_data(0x02);  // FLASH_PAGE_PROGRAM_OPCODE
//     ssp_put_data(addr >> 16);    // 地址高8位
//     ssp_put_data(addr >> 8);     // 地址中8位
//     ssp_put_data(addr);          // 地址低8位
//     ssp_enable();
    
//     // 逐字节写入数据
//     while(remaining_len > 0) {
//         // 等待FIFO有空间，添加超时保护
//         timeout_counter = 0;
//         while(ssp->status.tnf == 0) {  // 与dsp_program.c完全相同
//             timeout_counter++;
//             if(timeout_counter > 1000) {
//                 system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_SSP_CSN);
//                 ssp_disable();
//                 return -1;
//             }
//         }
        
//         // 写入一个字节
//         ssp->data.data = *data_ptr++;  // 与dsp_program.c完全相同
//         remaining_len--;
//     }
//     printf("External Flash data write completed\r\n");
    
//     // 等待SSP忙状态结束，添加超时保护
//     timeout_counter = 0;
//     while(ssp->status.bsy) {  // 与dsp_program.c完全相同
//         timeout_counter++;
//         if(timeout_counter > 10000) {
//             printf("External Flash write timeout: SSP busy\r\n");
//             system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_SSP_CSN);
//             ssp_disable();
//             return -1;
//         }
//     }
    
//     // 恢复CSN信号 - 拉高CSN
//     system_set_port_mux(GPIO_PORT_A, GPIO_BIT_1, PORTA1_FUNC_SSP_CSN);
//     ssp_disable();
    
//     // 等待Flash写入完成
//     flash_poll_busy_bit();
    
//     printf("External Flash write success at addr: 0x%08X, len: %d (Manual CSN)\r\n", addr, len);
//     return 0;
// }
// #endif 
